const MapValues = require('../template')

console.log("=== MapValues 基础测试 ===")

// 测试基本值映射
console.log(
  "基本值映射:", (() => {
    const obj = { a: 1, b: 2, c: 3 }
    const mapped = MapValues.mapValues(obj, value => value * 2)

    return typeof mapped === 'object' &&
      mapped.a === 2 &&
      mapped.b === 4 &&
      mapped.c === 6 &&
      'a' in mapped &&
      'b' in mapped &&
      'c' in mapped
  })()
)

// 测试字符串值映射
console.log(
  "字符串值映射:", (() => {
    const obj = { name: 'John', age: 30 }
    const mapped = MapValues.mapValues(obj, value => `user_${value}`)

    return typeof mapped === 'object' &&
      mapped.name === 'user_John' &&
      mapped.age === 'user_30' &&
      'name' in mapped &&
      'age' in mapped
  })()
)

// 测试类型转换映射
console.log(
  "类型转换映射:", (() => {
    const obj = { count: '5', price: '100', active: 'true' }
    const mapped = MapValues.mapValues(obj, value => {
      if (value === 'true') return true
      if (value === 'false') return false
      if (!isNaN(value)) return Number(value)
      return value
    })

    return typeof mapped === 'object' &&
      mapped.count === 5 &&
      mapped.price === 100 &&
      mapped.active === true &&
      'count' in mapped &&
      'price' in mapped &&
      'active' in mapped
  })()
)

// 测试条件值映射
console.log(
  "条件值映射:", (() => {
    const obj = { score: 85, grade: 'B', passed: true }
    const mapped = MapValues.mapValues(obj, value => {
      if (typeof value === 'number') return value >= 80 ? 'excellent' : 'good'
      if (typeof value === 'string') return value.toUpperCase()
      if (typeof value === 'boolean') return value ? 'yes' : 'no'
      return value
    })

    return typeof mapped === 'object' &&
      mapped.score === 'excellent' &&
      mapped.grade === 'B' &&
      mapped.passed === 'yes' &&
      'score' in mapped &&
      'grade' in mapped &&
      'passed' in mapped
  })()
)

// 测试空对象值映射
console.log(
  "空对象值映射:", (() => {
    const obj = {}
    const mapped = MapValues.mapValues(obj, value => value * 2)

    return typeof mapped === 'object' &&
      Object.keys(mapped).length === 0
  })()
)

// 测试单属性值映射
console.log(
  "单属性值映射:", (() => {
    const obj = { test: 'value' }
    const mapped = MapValues.mapValues(obj, value => value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped.test === 'VALUE' &&
      'test' in mapped
  })()
)

// 测试数字值映射
console.log(
  "数字值映射:", (() => {
    const obj = { 0: 'zero', 1: 'one', 2: 'two' }
    const mapped = MapValues.mapValues(obj, value => value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped[0] === 'ZERO' &&
      mapped[1] === 'ONE' &&
      mapped[2] === 'TWO' &&
      '0' in mapped &&
      '1' in mapped &&
      '2' in mapped
  })()
)

// 测试特殊字符键值映射
console.log(
  "特殊字符键值映射:", (() => {
    const obj = { 'key-with-dash': 'value1', 'key.with.dot': 'value2' }
    const mapped = MapValues.mapValues(obj, value => value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped['key-with-dash'] === 'VALUE1' &&
      mapped['key.with.dot'] === 'VALUE2' &&
      'key-with-dash' in mapped &&
      'key.with.dot' in mapped
  })()
)

// 测试布尔值映射
console.log(
  "布尔值映射:", (() => {
    const obj = { true: 'yes', false: 'no' }
    const mapped = MapValues.mapValues(obj, value => value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped.true === 'YES' &&
      mapped.false === 'NO' &&
      'true' in mapped &&
      'false' in mapped
  })()
)

// 测试空字符串值映射
console.log(
  "空字符串值映射:", (() => {
    const obj = { '': 'empty key', 'a': 'normal key' }
    const mapped = MapValues.mapValues(obj, value => value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped[''] === 'EMPTY KEY' &&
      mapped.a === 'NORMAL KEY' &&
      '' in mapped &&
      'a' in mapped
  })()
)

// 测试函数值映射
console.log(
  "函数值映射:", (() => {
    const func = () => 'hello'
    const obj = { method: func, data: 'value' }
    const mapped = MapValues.mapValues(obj, value => {
      if (typeof value === 'function') return value()
      return value.toUpperCase()
    })

    return typeof mapped === 'object' &&
      mapped.method === 'hello' &&
      mapped.data === 'VALUE' &&
      'method' in mapped &&
      'data' in mapped
  })()
)

// 测试对象值映射
console.log(
  "对象值映射:", (() => {
    const nested = { value: 'nested' }
    const obj = { nested: nested, simple: 'value' }
    const mapped = MapValues.mapValues(obj, value => {
      if (typeof value === 'object') return { ...value, mapped: true }
      return value.toUpperCase()
    })

    return typeof mapped === 'object' &&
      typeof mapped.nested === 'object' &&
      mapped.nested.value === 'nested' &&
      mapped.nested.mapped === true &&
      mapped.simple === 'VALUE' &&
      'nested' in mapped &&
      'simple' in mapped &&
      mapped.nested !== nested
  })()
)

// 测试数组值映射
console.log(
  "数组值映射:", (() => {
    const arr = [1, 2, 3]
    const obj = { items: arr, count: 3 }
    const mapped = MapValues.mapValues(obj, value => {
      if (Array.isArray(value)) return value.map(x => x * 2)
      return value * 2
    })

    return typeof mapped === 'object' &&
      Array.isArray(mapped.items) &&
      mapped.items[0] === 2 &&
      mapped.items[1] === 4 &&
      mapped.items[2] === 6 &&
      mapped.count === 6 &&
      'items' in mapped &&
      'count' in mapped &&
      mapped.items !== arr
  })()
)

// 测试null值映射
console.log(
  "null值映射:", (() => {
    const obj = { nullValue: null, normalValue: 'test' }
    const mapped = MapValues.mapValues(obj, value => value === null ? 'null' : value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped.nullValue === 'null' &&
      mapped.normalValue === 'TEST' &&
      'nullValue' in mapped &&
      'normalValue' in mapped
  })()
)

// 测试undefined值映射
console.log(
  "undefined值映射:", (() => {
    const obj = { undefinedValue: undefined, normalValue: 'test' }
    const mapped = MapValues.mapValues(obj, value => value === undefined ? 'undefined' : value.toUpperCase())

    return typeof mapped === 'object' &&
      mapped.undefinedValue === 'undefined' &&
      mapped.normalValue === 'TEST' &&
      'undefinedValue' in mapped &&
      'normalValue' in mapped
  })()
)

// 测试复杂对象值映射
console.log(
  "复杂对象值映射:", (() => {
    const obj = {
      user: { name: 'John', age: 30 },
      posts: [{ title: 'Post 1' }, { title: 'Post 2' }],
      meta: { count: 2 },
      settings: { theme: 'dark' }
    }
    const mapped = MapValues.mapValues(obj, value => {
      if (typeof value === 'object' && !Array.isArray(value)) {
        return { ...value, processed: true }
      }
      if (Array.isArray(value)) {
        return value.map(item => ({ ...item, processed: true }))
      }
      return value
    })

    return typeof mapped === 'object' &&
      typeof mapped.user === 'object' &&
      mapped.user.name === 'John' &&
      mapped.user.age === 30 &&
      mapped.user.processed === true &&
      Array.isArray(mapped.posts) &&
      mapped.posts[0].title === 'Post 1' &&
      mapped.posts[0].processed === true &&
      mapped.posts[1].title === 'Post 2' &&
      mapped.posts[1].processed === true &&
      typeof mapped.meta === 'object' &&
      mapped.meta.count === 2 &&
      mapped.meta.processed === true &&
      typeof mapped.settings === 'object' &&
      mapped.settings.theme === 'dark' &&
      mapped.settings.processed === true &&
      'user' in mapped &&
      'posts' in mapped &&
      'meta' in mapped &&
      'settings' in mapped
  })()
)

// 测试值映射保持键不变
console.log(
  "值映射保持键不变:", (() => {
    const obj = { a: 1, b: 2, c: 3 }
    const mapped = MapValues.mapValues(obj, value => value * 2)

    return 'a' in mapped &&
      'b' in mapped &&
      'c' in mapped &&
      Object.keys(mapped).length === 3
  })()
)

// 测试值映射函数参数
console.log(
  "值映射函数参数:", (() => {
    const obj = { a: 1, b: 2 }
    let callCount = 0
    const mapped = MapValues.mapValues(obj, (value, key) => {
      callCount++
      return `${key}:${value}`
    })

    return callCount === 2 &&
      mapped.a === 'a:1' &&
      mapped.b === 'b:2'
  })()
)

// 测试值映射返回相同值
console.log(
  "值映射返回相同值:", (() => {
    const obj = { a: 1, b: 2 }
    const mapped = MapValues.mapValues(obj, value => value)

    return mapped.a === 1 &&
      mapped.b === 2 &&
      mapped === obj // 应该是同一个对象
  })()
)

// 测试值映射返回undefined
console.log(
  "值映射返回undefined:", (() => {
    const obj = { a: 1, b: 2 }
    const mapped = MapValues.mapValues(obj, value => undefined)

    return typeof mapped === 'object' &&
      mapped.a === undefined &&
      mapped.b === undefined &&
      'a' in mapped &&
      'b' in mapped
  })()
)

// 测试值映射返回null
console.log(
  "值映射返回null:", (() => {
    const obj = { a: 1, b: 2 }
    const mapped = MapValues.mapValues(obj, value => null)

    return typeof mapped === 'object' &&
      mapped.a === null &&
      mapped.b === null &&
      'a' in mapped &&
      'b' in mapped
  })()
)

// 测试值映射返回函数
console.log(
  "值映射返回函数:", (() => {
    const obj = { a: 1, b: 2 }
    const mapped = MapValues.mapValues(obj, value => () => value)

    return typeof mapped === 'object' &&
      typeof mapped.a === 'function' &&
      typeof mapped.b === 'function' &&
      mapped.a() === 1 &&
      mapped.b() === 2 &&
      'a' in mapped &&
      'b' in mapped
  })()
)

// 测试值映射返回Symbol
console.log(
  "值映射返回Symbol:", (() => {
    const sym = Symbol('test')
    const obj = { a: 1, b: 2 }
    const mapped = MapValues.mapValues(obj, value => sym)

    return typeof mapped === 'object' &&
      mapped.a === sym &&
      mapped.b === sym &&
      'a' in mapped &&
      'b' in mapped
  })()
)

console.log("=== MapValues 基础测试完成 ===")
